﻿
/*
 * Copyright (C) 2011  Roy Sanchez
 * This program is free software; you can redistribute it and/or
 * modify it under the terms of the GNU General Public License
 * as published by the Free Software Foundation; either version 2
 * of the License, or (at your option) any later version.
 * 
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.

 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
 * 
 * 
 * +
 * if you find any bug or just have a question, can email me.
 * email : roygold8@gmail.com
 */

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Threading;

namespace FTP_Client
{
    public partial class ROftp : Form
    {
        DirectoryMapper Directory;
        FTP FtpClient;
        public delegate void ShowHistory();
        public ShowHistory Hist;
        Thread Historia;
        string Prueba;
        string prueba2;

        public ROftp()
        {
            Thread t = new Thread(new ThreadStart(LogoScreen));
            t.Start();
            
            Thread.Sleep(2000);
            InitializeComponent();
            t.Abort();
        }

        public void LogoScreen()
        {
            Application.Run(new LogoScreen());
        }

        private void ROftp_Load(object sender, EventArgs e)
        {

            Directory = new DirectoryMapper(tvLocal, tvRemoto);
            Directory.PC_Directory();
            Directory.PC_HomeDirectory();
            tbxLocal.Text = Directory.getCurrentPCdirectory();

            Hist = new ShowHistory(ShowHistoryMethod);
            Historia = new Thread(new ThreadStart(UpdateHistory));
            Historia.IsBackground = true;
            Historia.Start();

            
            rtbHistoria.ContextMenuStrip = cms_Historia;
            rtb_FilesHistory.ContextMenuStrip = cms_HistoryDU;


            cms_Historia.ItemClicked += new ToolStripItemClickedEventHandler(cms_Historia_ItemClicked);
            cms_HistoryDU.ItemClicked += new ToolStripItemClickedEventHandler(cms_HistoryDU_ItemClicked);
            
            
            /*
            rtbHistoria.Controls.Add(cms_Historia);
            rtb_FilesHistory.Controls.Add(cms_HistoryDU);
            
            
            if(cms_Historia != null)
                cms_Historia.Parent = rtbHistoria;
            if(cms_HistoryDU != null)
                cms_HistoryDU.Parent = rtb_FilesHistory;
            */
            tbx_Host.Focus();
            tbx_Host.KeyDown += new KeyEventHandler(tbx_Host_KeyDown);
            tbx_UserName.KeyDown += new KeyEventHandler(tbx_UserName_KeyDown);
            tbx_PassWord.KeyDown += new KeyEventHandler(tbx_PassWord_KeyDown);

        }

        void tbx_PassWord_KeyDown(object sender, KeyEventArgs e)
        {
            if (e.KeyCode == Keys.Enter)
            {
                if (!string.IsNullOrEmpty(tbx_Port.Text))
                    btnConectar.PerformClick();
                else
                    tbx_Port.Focus();
            }
        }


        void tbx_UserName_KeyDown(object sender, KeyEventArgs e)
        {
            if (e.KeyCode == Keys.Enter)
            {
                if (!string.IsNullOrEmpty(tbx_PassWord.Text) && !string.IsNullOrEmpty(tbx_Port.Text))
                {
                    btnConectar.PerformClick();
                }
                else if (string.IsNullOrEmpty(tbx_PassWord.Text))
                {
                    tbx_PassWord.Focus();
                }
                else
                {
                    tbx_Port.Focus();
                }
            }
        }

        void tbx_Host_KeyDown(object sender, KeyEventArgs e)
        {
            if (e.KeyCode == Keys.Enter)
            {
                if (!string.IsNullOrEmpty(tbx_UserName.Text) && !string.IsNullOrEmpty(tbx_PassWord.Text))
                {
                    btnConectar.PerformClick();
                }
                else if (string.IsNullOrEmpty(tbx_UserName.Text))
                {
                    tbx_UserName.Focus();
                }
                else
                {
                    tbx_PassWord.Focus();
                }
            }
        }

        void cms_HistoryDU_ItemClicked(object sender, ToolStripItemClickedEventArgs e)
        {
            lock (rtb_FilesHistory)
            {
                rtb_FilesHistory.SelectionStart = 0;
                rtb_FilesHistory.ScrollToCaret();
                rtb_FilesHistory.Clear();
                FtpClient.ClearHistoryDU();
            }
        }

        void cms_Historia_ItemClicked(object sender, ToolStripItemClickedEventArgs e)
        {
            lock (rtbHistoria)
            {
                rtbHistoria.SelectionStart = 0;
                rtbHistoria.ScrollToCaret();
                rtbHistoria.Clear();
                FtpClient.ClearHistory();
            }
        }

        private void btnConectar_Click(object sender, EventArgs e)
        {
            if (btnConectar.Text == "Connect")
            {
                //this.UseWaitCursor = true;
                ROftp.ActiveForm.UseWaitCursor = true;
                
                BackgroundWorker Conecta = new BackgroundWorker();

                Conecta.DoWork += new DoWorkEventHandler(Conecta_DoWork);
                Conecta.RunWorkerCompleted += new RunWorkerCompletedEventHandler(Conecta_RunWorkerCompleted);

                Conecta.RunWorkerAsync();

                /*
                FtpClient = new FTP(tbx_Host.Text, Convert.ToInt32(tbx_Port.Text),
                    tbx_UserName.Text, tbx_PassWord.Text);
                */
                
            }
            else if (btnConectar.Text == "Disconnect")
            {
                FtpClient.Logout();
                StopConnection();
                
            }
        }

        void Conecta_DoWork(object sender, DoWorkEventArgs e)
        {
            FtpClient = new FTP(tbx_Host.Text, Convert.ToInt32(tbx_Port.Text),
                    tbx_UserName.Text, tbx_PassWord.Text);

            if (!FtpClient.Connect())
            {
                e.Cancel = true;
            }

        }

        void Conecta_RunWorkerCompleted(object sender, RunWorkerCompletedEventArgs e)
        {

            if (e.Error == null && !e.Cancelled)
            {
                Directory.setFtpClient(FtpClient);
                Directory.RM_HomeDirectory();

                FtpClient.setType("I");

                FtpClient.SetPassiveMode();

                StartConnection();
                this.UseWaitCursor = false;
            }
            else
            {
                this.UseWaitCursor = false;
            }
        }


        public void ShowHistoryMethod()
        {
            string temp = string.Empty;

            if (FtpClient != null && FtpClient.getHistory() != string.Empty)
            {
                string cr = FtpClient.getHistory().Substring(FtpClient.getHistory().Length - 2, 2);
                
                //elimina la nueva linea, si esta al final
                if (cr == "\r\n")
                    temp = FtpClient.getHistory().Substring(0, FtpClient.getHistory().Length - 2);
                else
                    temp = FtpClient.getHistory();


                //historia ftp
                if (Prueba != temp)
                {
                    rtbHistoria.Text = temp;
                    rtbHistoria.SelectionStart = rtbHistoria.Text.Length;
                    rtbHistoria.ScrollToCaret();
                    Prueba = temp;
                }


                //historia descargas
                temp = FtpClient.getHistoryDU();
                if (prueba2 != temp)
                {
                    rtb_FilesHistory.Text = temp;
                    rtb_FilesHistory.SelectionStart = rtb_FilesHistory.Text.Length;
                    rtb_FilesHistory.ScrollToCaret();
                    prueba2 = temp;
                }

                //posicion directorio remoto
                /*
                temp = FtpClient.getCurrentDirectory();
                if (tbxRemoto.Text != temp)
                    tbxRemoto.Text = temp;
                 */

            }

            if (Directory != null)
            {
                
                if (Directory.isCanceled())
                {
                    Directory.StopCancel();
                    StopConnection();
                }
                
                 
                //posicion directorio local
                temp = Directory.getCurrentPCdirectory();
                if (tbxLocal.Text != temp)
                    tbxLocal.Text = temp;

                temp = Directory.getCurrentRMdirectory();
                if (tbxRemoto.Text != temp)
                    tbxRemoto.Text = temp;

                


            }

            if (Directory != null && FtpClient != null)
            {
                if (FtpClient.ArchivoEnviado)
                {
                    Directory.UpdateCurrentRMDirectory();
                    FtpClient.ArchivoEnviado = false;
                }

                if (FtpClient.ArchivoRecivido)
                {
                    Directory.UpdateCurrentPCDirectory();
                    FtpClient.ArchivoRecivido = false;
                }
            }

            

        }

        void UpdateHistory()
        {
            while (true)
            {
                try
                {
                    Invoke(Hist);
                }
                catch (Exception)
                {
                    break;
                }
                Thread.Sleep(100);
            }
        }

        ~ROftp()
        {
            Historia.Abort();
        }



        private void btnParent_Click(object sender, EventArgs e)
        {
            if (!FtpClient.VerifyConnection())
            {
                StopConnection();
                return;
            }
            Directory.ChangeToParentDirectory();
            //FtpClient.StructureMount("/");
        }

        private void btnUpload_Click(object sender, EventArgs e)
        {
            if (!FtpClient.VerifyConnection())
            {
                StopConnection();
                return;
            }
            File_Info Archivo = (File_Info)tvLocal.SelectedNode.Tag;
            File_Info DirectorioRM = (File_Info)tvRemoto.SelectedNode.Tag;

            
            
            FtpClient.UploadFile(Archivo, DirectorioRM, null);
        }

        void StartConnection()
        {
            btnConectar.Text = "Disconnect";

            btnParent.Enabled = true;
            btnUpload.Enabled = true;
            btnDownload.Enabled = true;
            btnDelete.Enabled = true;
            btnNewDirectory.Enabled = true;
        }

        void StopConnection()
        {

            Directory.ClearRM_Directory();
            Directory.ClearRMCurrentDirectory();

            btnConectar.Text = "Connect";

            tbxRemoto.Text = string.Empty;
            //tbxRemoto.Clear();

            btnParent.Enabled = false;
            btnUpload.Enabled = false;
            btnDownload.Enabled = false;
            btnDelete.Enabled = false;
            btnNewDirectory.Enabled = false;
        }

        private void btnDownload_Click(object sender, EventArgs e)
        {
            if (!FtpClient.VerifyConnection())
            {
                StopConnection();
                return;
            }
            File_Info Archivo = (File_Info)tvRemoto.SelectedNode.Tag;
            File_Info DirectorioPC = (File_Info)tvLocal.SelectedNode.Tag;

            FtpClient.DownloadFile(DirectorioPC, Archivo, null);
        }

        private void btnDelete_Click(object sender, EventArgs e)
        {
            File_Info info = (File_Info) tvRemoto.SelectedNode.Tag;
            DialogResult result;
            if (info.isFile)
            {
                result = MessageBox.Show("Borrar Archivo " + info.getName(), "Borrar Archivo",
                     MessageBoxButtons.OKCancel);

                if (result == System.Windows.Forms.DialogResult.OK)
                {
                    if (FtpClient.Delete(info.getPath()))
                        return;
                }
                else
                {
                    return;
                }
            }
            else if (info.isFolder)
            {
                result = MessageBox.Show("Borrar Diretorio " + info.getName(), "Borrar Archivo",
                     MessageBoxButtons.OKCancel);

                if (result == System.Windows.Forms.DialogResult.OK)
                {
                    if (FtpClient.RemoveDirectory(info.getPath()))
                        return;
                }
                else
                {
                    return;
                }
            }
            
        }

        private void btnNewDirectory_Click(object sender, EventArgs e)
        {
            NewDirectory pop = new NewDirectory();
            pop.StartPosition = FormStartPosition.CenterParent;
            DialogResult res = pop.ShowDialog(this);

            if (res == System.Windows.Forms.DialogResult.OK)
            {
                FtpClient.MakeDirectory(FtpClient.getCurrentDirectory() + pop.Resultado);
                Directory.UpdateCurrentRMDirectory();
            }
        }
    }
}
